import { _decorator, Component, director, find, instantiate, isValid, JsonAsset, Node, Prefab, Rect, Sprite, SpriteFrame, UITransform, Vec2 } from 'cc';
import bezier_data from 'db://assets/bezier/bezier_data';
import bezier_line from 'db://assets/bezier/bezier_line';
import { FishItem } from './FishItem';
import { Tools } from '../Tools';
import { CannonControl } from './CannonControl';
import { FishEvent } from '../Enums';
import { Global } from '../Global';
const { ccclass, property } = _decorator;

@ccclass('FishMgr')
export class FishMgr extends Component {

    @property(Prefab)
    private bezier_line_prefab: Prefab | null = null;

    lines: bezier_line[] = [];


    @property([JsonAsset])
    private jsons_track: JsonAsset[] = [];
    @property([Prefab])
    private fishsPre: Prefab[] = [];

    @property(UITransform)
    scene_mid:UITransform = null;
    scene_mid_rect: Rect = null;

    @property({ type: [SpriteFrame] })
    fish_life_Imgs: SpriteFrame[] = [];
    
    @property(JsonAsset)
    island_fish_json: JsonAsset = null;
    @property(JsonAsset)
    fishs_json: JsonAsset = null;

    /** 本关卡 需要的鱼的预制体 */
    private tLevel_fishsPre: Prefab[] = [];

    @property(Number)
    fish_new_num: number = 10;
    @property(Number)
    fish_new_one_max_num: number = 5;

    isTwo = false;

    fishs:FishItem[] = [];

    scene_UI:UITransform = null;
    
    line_index = 0;

    static Inst: FishMgr = null;


    onLoad() {
        FishMgr.Inst = this;

        this.getJsonData();
    }

    async start() {
        const _height = Tools.scene_height_extra() / 2;//矩形检测适配场景
        this.scene_mid.height += _height;
        this.scene_mid_rect = this.scene_mid.getComponent(UITransform).getBoundingBoxToWorld();

        this.scene_UI = find('Canvas').getComponent(UITransform);

        await this.drawBezierLineByJsonData();

        this.runBezierLine()

        //检查 d2f4g
        // this.schedule(()=>{
        //     this.findScene_middle();
        // } , 3)
    }

    /** 隐藏所有鱼 */
    hideFishs(){
        this.fishs.forEach(element => {
            element.deathAnim(false);
        });
    }

    getJsonData(){
        let island_index = -1

        const cur_level = Global.cur_lvl_index + 1;
        console.log("cur_level: ",cur_level)

        const json = this.island_fish_json.json
        for (let i = 0; i < json.length; i++) {
            const range = (json[i].level + '').split("-");
            console.log(range)
            if(cur_level >= Number(range[0]) && cur_level <= Number(range[1])){
                island_index = i
                break;
            }
        }

        console.log(" id: ",json[island_index].id," name: ",json[island_index].name)

        for (let i = 0; i < json[island_index].fish.length; i++) {
            const _index = json[island_index].fish[i] - 1
            if(this.fishsPre[_index])
                this.tLevel_fishsPre.push(this.fishsPre[_index])
        }

        console.log(this.tLevel_fishsPre)
    }

    /** 运行 */
    private runBezierLine() {
        let mid_start_num = 3
        
        let fish_index = 0;
        for (let i = 0; i < this.fish_new_num; i++) {
            const _fish = instantiate(this.tLevel_fishsPre[fish_index]);//生成鱼
            _fish.parent = this.node;

            // 线路随机不重复
            if(this.line_index >= this.jsons_track.length){
                this.line_index = 0
            }
            const _line = this.lines[this.line_index];
            let _random = Math.floor(Math.random() * 4 + 1);//随机生成时间

            const runSpeed = 100 - (fish_index*8);

            let is_midStart = false;
            if(mid_start_num > 0){
                mid_start_num--;
                is_midStart = true;
                _random = 0
            }

            this.scheduleOnce(() => _line.runNode(runSpeed, _fish , is_midStart), _random);//越大游动越慢
            this.line_index++;
            //----------------------            

            let fishItem = _fish.getComponent(FishItem);
            if(!fishItem){
                fishItem = _fish.addComponent(FishItem);
            }
            fishItem.setLine(_line)
            fishItem.runSpeed = runSpeed
            this.fishs.push(fishItem);//添加+鱼


            //配置json 此鱼爆出的金币 fish_index 关联 islandFish[关卡].fish[] 的索引
            const json = this.fishs_json.json
            fishItem.generate_coin = json[fish_index].coin

            
            // fish_index 写在用到的最后
            fish_index++;
            if (fish_index >= this.tLevel_fishsPre.length) fish_index = 0;
            if(this.isTwo){
                if (fish_index >= this.fish_new_one_max_num) fish_index = 0;
            }
            if(this.tLevel_fishsPre.length -1 == fish_index)this.isTwo = true;//进入二次循环生成

        }
    }

    /** 一条鱼游动结束后，重新开始新路线 */
    async runRestart(speed: number, _fish: Node) {
        // 线路随机不重复
        if (this.line_index >= this.jsons_track.length) {
            this.line_index = 0
        }
        const _json = this.jsons_track[this.line_index].json[0];
        let _line =await this.newLine(_json);
        this.line_index++;

        //console.log("*** " , _line.bezierPoints)

        let _random = Math.floor(Math.random() * 1 + 1);
        this.scheduleOnce(() => _line.runNode(speed, _fish), _random);

        _fish.getComponent(FishItem).setLine(_line)
    }

    private async drawBezierLineByJsonData() {
        //打乱路线
        Tools.shuffle(this.jsons_track);
        for (let i = 0; i < this.jsons_track.length; i++) {
            const _json = this.jsons_track[i].json[0];
            // console.log(_json)

           await this.newLine(_json);
        }
    }

    newLine(_json: any) {
        return new Promise<bezier_line>(resolve => {
            const lineNode = instantiate(this.bezier_line_prefab);
            lineNode.parent = this.node;

            let _height_half = (this.scene_UI.height - 1400) / 2;
            lineNode.setPosition(_json.LP[0], _json.LP[1] + _height_half);//设置线的总点
            const _fishLine = lineNode.getComponent(bezier_line);
            _fishLine.initWithPositionArray_any(_json.PP)

            bezier_data.curBezierLineIndex = 0;

            this.lines.push(_fishLine);

            resolve(_fishLine);
        })

    }

    removeLine(bline:bezier_line){
        for (let i = 0; i < this.lines.length; i++) {
            const _line = this.lines[i];
            if (bline == _line) {
                this.lines.splice(i, 1)
                bline.destroy();
                break;
            }
        }
    }

    /** 找到在鱼游动在路线中间段的那些 out*/
    findProgress_median(){
        let _fishs:FishItem[] = [];
        for (let i = 0; i < this.fishs.length; i++) {
            const _fish = this.fishs[i];
            if(_fish.line.progress > 0.2 && _fish.line.progress < 0.8){
                _fishs.push(_fish)
            }
        }

        return _fishs;
    }

    /** 找到场景中的鱼 */
    findScene_middle(){
        let _fishs: FishItem[] = [];
        for (let i = 0; i < this.fishs.length; i++) {
            const _fish = this.fishs[i];
            const _pos = _fish.node.getWorldPosition();
            let isMid = this.scene_mid_rect.contains(Tools.V3ToV2(_pos))
            if (isMid && _fish.life_val > 0) {
                _fishs.push(_fish)

                //检查 d2f4g
                // _fish.node.active = false;
                // this.scheduleOnce(()=>{
                //     _fish.node.active = true;
                // }, 1)
            }
        }

        return _fishs;
    }

    
    /** 找到线路最近的一条鱼(角度最小就是最近) */
    findLine_near(_fishs:FishItem[]){
        const p1 = CannonControl.Inst.node.getWorldPosition();
        const p2 = CannonControl.Inst.muzzle.getWorldPosition();
        const x1 = p2.subtract(p1);

        let cur_angle = 90;//应该不会超过90°
        let cur_index = -1;
        for (let i = 0; i < _fishs.length; i++) {
            const _fish = _fishs[i];
            //死鱼跳出此次循环
            if(_fish.life_val <= 0)continue;

            const _fish_pos = _fish.node.getWorldPosition();
            const x2 = _fish_pos.subtract(p1);
            let _angle = Math.abs(Tools.getAngle(x1, x2));
            //console.log(_angle)
            if(_angle < cur_angle){
                cur_angle = _angle;
                cur_index = i;
            }
        }

        if(cur_index == -1)return null;

        return _fishs[cur_index];//--->(待写)ps：如果鱼血量多时，是否标记此鱼，下次也进行击打，直到打死
    }

}


